package org.vt.eldercare.serial;

import org.jfree.data.time.Millisecond;
import org.vt.eldercare.data.DataPoint;
import org.vt.eldercare.data.Node;

public class SerialInterpreter {

	private String data;

	public SerialInterpreter(String input) {
		this.data = input;
	}

	public int getNode() {
		return (0x07) & (data.charAt(0) >> 5);
	}

	public int getAccelX() {
		return (((0x1F) & (data.charAt(0))) << 5)
				| (((0xF8) & (data.charAt(1))) >> 3);
	}

	public int getAccelY() {
		return (((0x07) & (data.charAt(1))) << 7)
				| (((0xFE) & (data.charAt(2))) >> 1);
	}

	public int getAccelZ() {
		return (((0x01) & (data.charAt(2))) << 9) | ((data.charAt(3)) << 1)
				| ((0x80) & (data.charAt(4))) >> 7;
	}

	public byte getRssi() {
		return (byte) ((((0x7F) & (data.charAt(4))) << 1) | (((0x80) & (data
				.charAt(5))) >> 7));
	}

	public short getGyroX() {
		return (short) ((((0x7F) & (data.charAt(5))) << 9)
				| (data.charAt(6) << 1) | (((0x80) & (data.charAt(7))) >> 7));
	}

	public short getGyroY() {
		return (short) ((((0x7F) & (data.charAt(7))) << 9)
				| (data.charAt(8) << 1) | (((0x80) & (data.charAt(9))) >> 7));
	}

	public short getGyroZ() {
		return (short) ((((0x7F) & (data.charAt(9))) << 9)
				| (data.charAt(10) << 1) | (((0x80) & (data.charAt(11))) >> 7));
	}

	public int printStatus() {
		return (0x7F) & data.charAt(11);
	}
	
	public void updateNodeStatus(Node n){
		byte flags = (byte) ((0x3F) & data.charAt(11));
		Node.Status status = n.getStatus();
		status.setAccelZEnabled((flags & 0x20) != 0);
		status.setAccelYEnabled((flags & 0x10) != 0);
		status.setAccelXEnabled((flags & 0x08) != 0);
		status.setGyroZEnabled((flags & 0x04) != 0);
		status.setGyroYEnabled((flags & 0x02) != 0);
		status.setGyroXEnabled((flags & 0x01) != 0);
	}

	public DataPoint getDataPoint() {
		return new DataPoint(getAccelX(), getGyroX(), getAccelY(), getGyroY(),
				getAccelZ(), getGyroZ(), new Millisecond());
	}

	public String outputAsString() {
		return "aX: " + getAccelX() + " aY: " + getAccelY() + " aZ: "
				+ getAccelZ() + " rssi: " + getRssi() + " gX: " + getGyroX()
				+ " gY: " + getGyroY() + " gZ: " + getGyroZ() + " Status: "
				+ printStatus();
	}
}
